home *** CD-ROM | disk | FTP | other *** search
/ Amiga Format CD 38 / Amiga Format CD38 (1999-03-15)(Future Publishing)(GB)(Track 1 of 3)[!][issue 1999-04].iso / -seriously_amiga- / programming / other / cyberxxxsrc / cyberqt / txt / cyberqtparser.mod < prev    next >
Text File  |  1999-02-08  |  26KB  |  824 lines

  1. MODULE  CyberQTParser;
  2.  
  3. (* $IFNOT DEBUG *)
  4.   (* $StackChk- $OvflChk- $RangeChk- $CaseChk- $ReturnChk- $NilChk- $TypeChk- $OddChk- $ClearVars- *)
  5. (* $END *)
  6.  
  7. (* /// ------------------------------- "IMPORT" -------------------------------- *)
  8. IMPORT  cu:=CyberQTUtils,
  9.         d:=Dos,
  10.         e:=Exec,
  11.         es:=ExecSupport,
  12.         fp:=FixedPoint,
  13.         g:=CyberQTGlobals,
  14.         io:=AsyncIOSupport2,
  15.         mu:=MathUtils,
  16.         o:=CyberQTOpts,
  17.         ol:=OberonLib,
  18.         y:=SYSTEM;
  19. (* \\\ ------------------------------------------------------------------------- *)
  20.  
  21. (* /// -------------------------------- "CONST" -------------------------------- *)
  22. CONST   idchap=y.VAL(LONGINT,"chap");
  23.         idclip=y.VAL(LONGINT,"clip");
  24.         idcrng=y.VAL(LONGINT,"crng");
  25.         idctab=y.VAL(LONGINT,"ctab");
  26.         iddinf=y.VAL(LONGINT,"dinf");
  27.         iddref=y.VAL(LONGINT,"dref");
  28.         idedts=y.VAL(LONGINT,"edts");
  29.         idelst=y.VAL(LONGINT,"elst");
  30.         idgmhd=y.VAL(LONGINT,"gmhd");
  31.         idgmin=y.VAL(LONGINT,"gmin");
  32.         idhdlr=y.VAL(LONGINT,"hdlr");
  33.         idimap=y.VAL(LONGINT,"imap");
  34.         idkmat=y.VAL(LONGINT,"kmat");
  35.         idload=y.VAL(LONGINT,"load");
  36.         idmatt=y.VAL(LONGINT,"matt");
  37.         idmdhd=y.VAL(LONGINT,"mdhd");
  38.         idmdia=y.VAL(LONGINT,"mdia");
  39.         idminf=y.VAL(LONGINT,"minf");
  40.         idmvhd=y.VAL(LONGINT,"mvhd");
  41.         idscpt=y.VAL(LONGINT,"scpt");
  42.         idskip=y.VAL(LONGINT,"skip");
  43.         idsmhd=y.VAL(LONGINT,"smhd");
  44.         idssrc=y.VAL(LONGINT,"ssrc");
  45.         idstbl=y.VAL(LONGINT,"stbl");
  46.         idstco=y.VAL(LONGINT,"stco");
  47.         idstgs=y.VAL(LONGINT,"stgs");
  48.         idstsc=y.VAL(LONGINT,"stsc");
  49.         idstsd=y.VAL(LONGINT,"stsd");
  50.         idstsh=y.VAL(LONGINT,"stsh");
  51.         idstss=y.VAL(LONGINT,"stss");
  52.         idstsz=y.VAL(LONGINT,"stsz");
  53.         idstts=y.VAL(LONGINT,"stts");
  54.         idsync=y.VAL(LONGINT,"sync");
  55.         idtkhd=y.VAL(LONGINT,"tkhd");
  56.         idtmcd=y.VAL(LONGINT,"tmcd");
  57.         idtrak=y.VAL(LONGINT,"trak");
  58.         idtref=y.VAL(LONGINT,"tref");
  59.         idudta=y.VAL(LONGINT,"udta");
  60.         idvmhd=y.VAL(LONGINT,"vmhd");
  61.  
  62.         trackEnabled=0;
  63.         trackInMovie=1;
  64.         trackInPreview=2;
  65.         trackInPoster=3;
  66. (* \\\ ------------------------------------------------------------------------- *)
  67.  
  68. (* /// --------------------------------- "VAR" --------------------------------- *)
  69. VAR     currentTrack: g.TrackPtr;
  70.         videoFlag: BOOLEAN;
  71.         audioFlag: BOOLEAN;
  72.         trackHead: g.TrackHeader;
  73.         mediaHead: g.MediaHeader;
  74.         trackStartOffset: LONGINT;
  75.         trackInitDuration: LONGINT;
  76.         edits: g.EditListIndex;
  77.         editEntries: LONGINT;
  78. (* \\\ ------------------------------------------------------------------------- *)
  79.  
  80. (* /// ------------------- "PROCEDURE CorrectTrackValues()" -------------------- *)
  81. PROCEDURE CorrectTrackValues(VAR trackList: e.List);
  82.  
  83. VAR     track: g.TrackPtr;
  84.         cnt: LONGINT;
  85.         lastCodec: LONGINT;
  86.         lastChunk: LONGINT;
  87. BEGIN
  88.   IF es.ListEmpty(trackList) THEN RETURN; END;
  89.   track:=trackList.head;
  90.   lastCodec:=-1;
  91.   lastChunk:=-1;
  92.   WHILE track.node.succ#NIL DO
  93.     IF track.syncs#NIL THEN
  94.       FOR cnt:=0 TO track.syncEntries-1 DO
  95.         DEC(track.syncs[cnt]);
  96.       END;
  97.     END;
  98.     FOR cnt:=0 TO track.sampleEntries-1 DO
  99.       INC(track.samples[cnt].descriptionID,lastCodec);
  100.       INC(track.samples[cnt].firstChunk,lastChunk);
  101.     END;
  102.     INC(lastCodec,track.descriptionEntries);
  103.     INC(lastChunk,track.samples[track.sampleEntries-1].firstChunk);
  104.     track:=track.node.succ;
  105.   END;
  106. END CorrectTrackValues;
  107. (* \\\ ------------------------------------------------------------------------- *)
  108.  
  109. (* /// "STBL" *)
  110. (* /// ------------------------ "PROCEDURE ReadSTSD()" ------------------------- *)
  111. PROCEDURE ReadSTSD(size: LONGINT): BOOLEAN;
  112.  
  113. VAR     entries: LONGINT;
  114.         cnt: LONGINT;
  115.         head: g.DescriptionHead;
  116.         desc: g.DummyDescriptionPtr;
  117.  
  118. BEGIN
  119.   io.Skip(g.qtFile,4); (* version/flags *)
  120.   entries:=io.GetMSBLong(g.qtFile);
  121.   DEC(size,8);
  122.   ol.New(currentTrack.descriptions,entries*SIZE(g.DummyDescriptionPtr));
  123.   currentTrack.descriptionEntries:=entries;
  124.   FOR cnt:=0 TO entries-1 DO
  125.     io.Read(g.qtFile,y.ADR(head),SIZE(head));
  126.     ol.New(desc,head.size);
  127.     desc.head:=head;
  128.     io.Read(g.qtFile,y.ADR(desc.data),head.size-SIZE(head));
  129.     DEC(size,head.size);
  130.     currentTrack.descriptions[cnt]:=desc;
  131.   END;
  132.   IF size>0 THEN io.Skip(g.qtFile,size); END;
  133.   RETURN TRUE;
  134. END ReadSTSD;
  135. (* \\\ ------------------------------------------------------------------------- *)
  136.  
  137. (* /// ------------------------ "PROCEDURE ReadSTTS()" ------------------------- *)
  138. PROCEDURE ReadSTTS(size: LONGINT): BOOLEAN;
  139.  
  140. VAR     index: g.TimeToSampleIndex;
  141.         entries: LONGINT;
  142.         cnt: LONGINT;
  143.  
  144. BEGIN
  145.   IF ~videoFlag THEN io.Skip(g.qtFile,size); RETURN TRUE; END;
  146.   io.Skip(g.qtFile,4); (* version/flags *)
  147.   entries:=io.GetMSBLong(g.qtFile);
  148.   DEC(size,8);
  149.   ol.New(index,entries*SIZE(g.TimeToSample));
  150.   io.Read(g.qtFile,index,entries*SIZE(g.TimeToSample));
  151.   DEC(size,entries*SIZE(g.TimeToSample));
  152.   currentTrack.times:=index;
  153.   currentTrack.timeEntries:=entries;
  154.   IF size>0 THEN io.Skip(g.qtFile,size); END;
  155.   RETURN TRUE;
  156. END ReadSTTS;
  157. (* \\\ ------------------------------------------------------------------------- *)
  158.  
  159. (* /// ------------------------ "PROCEDURE ReadSTSS()" ------------------------- *)
  160. PROCEDURE ReadSTSS(size: LONGINT): BOOLEAN;
  161.  
  162. VAR     index: g.SyncSampleIndex;
  163.         entries: LONGINT;
  164.         cnt: LONGINT;
  165.  
  166. BEGIN
  167.   io.Skip(g.qtFile,4); (* version/flags *)
  168.   entries:=io.GetMSBLong(g.qtFile);
  169.   DEC(size,8);
  170.   ol.New(index,entries*SIZE(LONGINT));
  171.   io.Read(g.qtFile,index,entries*SIZE(LONGINT));
  172.   DEC(size,entries*SIZE(LONGINT));
  173.   currentTrack.syncEntries:=entries;
  174.   currentTrack.syncs:=index;
  175.   IF size>0 THEN io.Skip(g.qtFile,size); END;
  176.   RETURN TRUE;
  177. END ReadSTSS;
  178. (* \\\ ------------------------------------------------------------------------- *)
  179.  
  180. (* /// ------------------------ "PROCEDURE ReadSTSC()" ------------------------- *)
  181. PROCEDURE ReadSTSC(size: LONGINT): BOOLEAN;
  182.  
  183. VAR     index: g.SampleToChunkIndex;
  184.         entries: LONGINT;
  185.         cnt: LONGINT;
  186.         last: LONGINT;
  187.  
  188. BEGIN
  189.   io.Skip(g.qtFile,4); (* version/flags *)
  190.   entries:=io.GetMSBLong(g.qtFile);
  191.   DEC(size,8);
  192.   IF entries#0 THEN
  193.     cnt:=size DIV entries;
  194.   ELSE
  195.     cnt:=0;
  196.   END;
  197.   ol.New(index,entries*SIZE(g.SampleToChunk));
  198.   IF cnt=16 THEN (* old style STSC *)
  199.     FOR cnt:=0 TO entries-1 DO
  200.       index[cnt].firstChunk:=io.GetMSBLong(g.qtFile);
  201.       io.Skip(g.qtFile,4);
  202.       index[cnt].samplesPerChunk:=io.GetMSBLong(g.qtFile);
  203.       index[cnt].descriptionID:=io.GetMSBLong(g.qtFile);
  204.       DEC(size,16);
  205.     END;
  206.   ELSE
  207.     io.Read(g.qtFile,index,entries*SIZE(g.SampleToChunk));
  208.     DEC(size,entries*SIZE(g.SampleToChunk));
  209.   END;
  210.   currentTrack.samples:=index;
  211.   currentTrack.sampleEntries:=entries;
  212.   IF size>0 THEN io.Skip(g.qtFile,size); END;
  213.   RETURN TRUE;
  214. END ReadSTSC;
  215. (* \\\ ------------------------------------------------------------------------- *)
  216.  
  217. (* /// ------------------------ "PROCEDURE ReadSTSZ()" ------------------------- *)
  218. PROCEDURE ReadSTSZ(size: LONGINT): BOOLEAN;
  219.  
  220. VAR     index: g.SampleSizeIndex;
  221.         entries: LONGINT;
  222.         sampleSize: LONGINT;
  223.         cnt: LONGINT;
  224.  
  225. BEGIN
  226.   io.Skip(g.qtFile,4); (* version/flags *)
  227.   sampleSize:=io.GetMSBLong(g.qtFile);
  228.   entries:=io.GetMSBLong(g.qtFile);
  229.   DEC(size,12);
  230.   IF sampleSize=0 THEN
  231.     ol.New(index,entries*SIZE(LONGINT));
  232.     io.Read(g.qtFile,index,entries*SIZE(LONGINT));
  233.     DEC(size,entries*SIZE(LONGINT));
  234.   ELSIF (sampleSize=1) OR (sampleSize=2) THEN (* 1 für 8bit, 2 für 16bit *)
  235.     ol.New(index,SIZE(LONGINT));
  236.     index[0]:=entries;
  237.     entries:=sampleSize;
  238.   ELSE
  239.     ol.New(index,entries*SIZE(LONGINT));
  240.     FOR cnt:=0 TO entries-1 DO index[cnt]:=sampleSize; END;
  241.   END;
  242.   currentTrack.sizes:=index;
  243.   currentTrack.sizeEntries:=entries;
  244.   IF size>0 THEN io.Skip(g.qtFile,size); END;
  245.   RETURN TRUE;
  246. END ReadSTSZ;
  247. (* \\\ ------------------------------------------------------------------------- *)
  248.  
  249. (* /// ------------------------ "PROCEDURE ReadSTCO()" ------------------------- *)
  250. PROCEDURE ReadSTCO(size: LONGINT): BOOLEAN;
  251.  
  252. VAR     index: g.ChunkOffsetIndex;
  253.         entries: LONGINT;
  254.  
  255. BEGIN
  256.   io.Skip(g.qtFile,4); (* version/flags *)
  257.   entries:=io.GetMSBLong(g.qtFile);
  258.   DEC(size,8);
  259.   ol.New(index,entries*SIZE(LONGINT));
  260.   io.Read(g.qtFile,index,entries*SIZE(LONGINT));
  261.   DEC(size,entries*SIZE(LONGINT));
  262.   currentTrack.offsets:=index;
  263.   currentTrack.offsetEntries:=entries;
  264.   IF size>0 THEN io.Skip(g.qtFile,size); END;
  265.   RETURN TRUE;
  266. END ReadSTCO;
  267. (* \\\ ------------------------------------------------------------------------- *)
  268.  
  269. (* /// ------------------------ "PROCEDURE ReadSTGS()" ------------------------- *)
  270. PROCEDURE ReadSTGS(size: LONGINT): BOOLEAN;
  271.  
  272. VAR     index: g.ChunkOffsetIndex;
  273.         entries: LONGINT;
  274.         cnt: LONGINT;
  275.  
  276. BEGIN
  277.   io.Skip(g.qtFile,4); (* version/flags *)
  278.   entries:=io.GetMSBLong(g.qtFile);
  279.   DEC(size,8);
  280. (*
  281.   FOR cnt:=0 TO entries-1 DO
  282.     d.PrintF("samps: %ld\n",io.GetMSBLong());
  283.     d.PrintF("pad: %ld\n", io.GetMSBLong());
  284.     DEC(size,8);
  285.   END;
  286. *)
  287.   io.Skip(g.qtFile,size); size:=0;
  288.   IF size>0 THEN io.Skip(g.qtFile,size); END;
  289.   RETURN TRUE;
  290. END ReadSTGS;
  291. (* \\\ ------------------------------------------------------------------------- *)
  292.  
  293. (* /// ------------------------ "PROCEDURE ParseSTBL()" ------------------------ *)
  294. PROCEDURE ParseSTBL(size: LONGINT): LONGINT;
  295.  
  296. VAR     atom: g.Atom;
  297.         errVal: LONGINT;
  298.  
  299. BEGIN
  300.   errVal:=g.noError;
  301.   IF ~(videoFlag OR audioFlag) THEN
  302.     io.Skip(g.qtFile,size);
  303.     RETURN errVal;
  304.   END;
  305.   WHILE (size>0) & (errVal=g.noError) DO
  306.     io.Read(g.qtFile,y.ADR(atom),SIZE(atom));
  307.     DEC(size,atom.size);
  308.     DEC(atom.size,SIZE(atom));
  309. (* /// "$IF RUNDEBUG" *)
  310.     IF o.debug THEN
  311.       d.PrintF("          stbl id: "); cu.PrintFCC(atom.id); d.PrintF(", size: %ld\n",atom.size);
  312.     END;
  313. (* \\\ $END *)
  314.     CASE atom.id OF
  315.     | idstsd: IF ~ReadSTSD(atom.size) THEN errVal:=g.unknownError; END;
  316.     | idstts: IF ~ReadSTTS(atom.size) THEN errVal:=g.unknownError; END;
  317.     | idstss: IF ~ReadSTSS(atom.size) THEN errVal:=g.unknownError; END;
  318.     | idstsc: IF ~ReadSTSC(atom.size) THEN errVal:=g.unknownError; END;
  319.     | idstsz: IF ~ReadSTSZ(atom.size) THEN errVal:=g.unknownError; END;
  320.     | idstco: IF ~ReadSTCO(atom.size) THEN errVal:=g.unknownError; END;
  321.     | idstgs: IF ~ReadSTGS(atom.size) THEN errVal:=g.unknownError; END;
  322.     | idstsh: io.Skip(g.qtFile,atom.size);
  323.     ELSE
  324. (* /// "$IF RUNDEBUG" *)
  325.       IF o.debug THEN d.PrintF("unknown dinf atom\n"); END;
  326. (* \\\ $END *)
  327.       io.Skip(g.qtFile,atom.size);
  328.     END;
  329.  
  330.     IF d.ctrlC IN e.SetSignal(LONGSET{},LONGSET{d.ctrlC}) THEN errVal:=d.break; END;
  331.     IF ~g.qtFile.readOk THEN errVal:=g.readError; END;
  332.   END;
  333.  
  334.   RETURN errVal;
  335. END ParseSTBL;
  336. (* \\\ ------------------------------------------------------------------------- *)
  337. (* \\\ *)
  338.  
  339. (* /// "MINF" *)
  340. (* /// ------------------------ "PROCEDURE ReadVMHD()" ------------------------- *)
  341. PROCEDURE ReadVMHD(size: LONGINT): BOOLEAN;
  342.  
  343. VAR     head: g.VideoMediaHeader;
  344.         newTrack: g.TrackPtr;
  345.  
  346. BEGIN
  347.   IF size#SIZE(head) THEN
  348.     d.PrintF("wrong size\n");
  349.     RETURN FALSE;
  350.   END;
  351.   io.Read(g.qtFile,y.ADR(head),size);
  352. (* /// "$IF RUNDEBUG" *)
  353.   IF o.debug THEN
  354.     d.PrintF("          version: %ld\n"
  355.              "          flags: $%06lx\n"
  356.              "          graphics mode: %ld\n"
  357.              "          opColors: %ld %ld %ld\n"
  358.              "\n",y.LSH(head.version,-24),
  359.                   head.version MOD y.LSH(1,24),
  360.                   head.graphicsMode,
  361.                   head.opColor[0],
  362.                   head.opColor[1],
  363.                   head.opColor[2]);
  364.   END;
  365. (* \\\ $END *)
  366.  
  367.   videoFlag:=TRUE;
  368.   NEW(newTrack);
  369.   newTrack.head:=trackHead;
  370.   newTrack.mediaHead:=mediaHead;
  371.   newTrack.startOffset:=trackStartOffset;
  372.   newTrack.initDuration:=trackInitDuration;
  373.   newTrack.edits:=edits;
  374.   newTrack.editEntries:=editEntries;
  375.   e.AddTail(g.animInfo.videoTracks,newTrack);
  376.   currentTrack:=newTrack;
  377.  
  378.   RETURN TRUE;
  379. END ReadVMHD;
  380. (* \\\ ------------------------------------------------------------------------- *)
  381.  
  382. (* /// ------------------------ "PROCEDURE ReadSMHD()" ------------------------- *)
  383. PROCEDURE ReadSMHD(size: LONGINT): BOOLEAN;
  384.  
  385. VAR     head: g.SoundMediaHeader;
  386.         newTrack: g.TrackPtr;
  387.  
  388. BEGIN
  389.   IF size#SIZE(head) THEN
  390.     d.PrintF("wrong size\n");
  391.     RETURN FALSE;
  392.   END;
  393.   io.Read(g.qtFile,y.ADR(head),size);
  394. (* /// "$IF RUNDEBUG" *)
  395.   IF o.debug THEN
  396.     d.PrintF("          version: %ld\n"
  397.              "          flags: $%06lx\n"
  398.              "          balance: %ld\n"
  399.              "\n",y.LSH(head.version,-24),
  400.                   head.version MOD y.LSH(1,24),
  401.                   head.balance);
  402.   END;
  403. (* \\\ $END *)
  404.  
  405.   audioFlag:=TRUE;
  406.   NEW(newTrack);
  407.   newTrack.head:=trackHead;
  408.   newTrack.mediaHead:=mediaHead;
  409.   newTrack.startOffset:=trackStartOffset;
  410.   newTrack.initDuration:=trackInitDuration;
  411.   newTrack.edits:=edits;
  412.   newTrack.editEntries:=editEntries;
  413.   e.AddTail(g.animInfo.audioTracks,newTrack);
  414.   currentTrack:=newTrack;
  415.  
  416.   RETURN TRUE;
  417. END ReadSMHD;
  418. (* \\\ ------------------------------------------------------------------------- *)
  419.  
  420. (* /// ------------------------ "PROCEDURE ParseMINF()" ------------------------ *)
  421. PROCEDURE ParseMINF(size: LONGINT): LONGINT;
  422.  
  423. VAR     atom: g.Atom;
  424.         errVal: LONGINT;
  425.  
  426. BEGIN
  427.   errVal:=g.noError;
  428.   WHILE (size>0) & (errVal=g.noError) DO
  429.     io.Read(g.qtFile,y.ADR(atom),SIZE(atom));
  430.     DEC(size,atom.size);
  431.     DEC(atom.size,SIZE(atom));
  432. (* /// "$IF RUNDEBUG" *)
  433.     IF o.debug THEN
  434.       d.PrintF("        minf id: "); cu.PrintFCC(atom.id); d.PrintF(", size: %ld\n",atom.size);
  435.     END;
  436. (* \\\ $END *)
  437.     CASE atom.id OF
  438.     | idvmhd: IF ~ReadVMHD(atom.size) THEN errVal:=g.unknownError; END;
  439.     | idsmhd: IF ~ReadSMHD(atom.size) THEN errVal:=g.unknownError; END;
  440.     | idstbl: errVal:=ParseSTBL(atom.size);
  441.     | iddinf,
  442.       idhdlr,
  443.       idgmhd: io.Skip(g.qtFile,atom.size);
  444.     ELSE
  445. (* /// "$IF RUNDEBUG" *)
  446.       IF o.debug THEN d.PrintF("unknown minf atom\n"); END;
  447. (* \\\ $END *)
  448.       io.Skip(g.qtFile,atom.size);
  449.     END;
  450.  
  451.     IF d.ctrlC IN e.SetSignal(LONGSET{},LONGSET{d.ctrlC}) THEN errVal:=d.break; END;
  452.     IF ~g.qtFile.readOk THEN errVal:=g.readError; END;
  453.   END;
  454.   RETURN errVal;
  455. END ParseMINF;
  456. (* \\\ ------------------------------------------------------------------------- *)
  457. (* \\\ *)
  458.  
  459. (* /// "MDIA" *)
  460. (* /// ------------------------ "PROCEDURE ReadMDHD()" ------------------------- *)
  461. PROCEDURE ReadMDHD(size: LONGINT): BOOLEAN;
  462.  
  463. VAR     head: g.MediaHeader;
  464.  
  465. BEGIN
  466.   IF size#SIZE(head) THEN
  467.     d.PrintF("wrong size\n");
  468.     RETURN FALSE;
  469.   END;
  470.   io.Read(g.qtFile,y.ADR(head),size);
  471. (* /// "$IF RUNDEBUG" *)
  472.   IF o.debug THEN
  473.     d.PrintF("        version: %ld\n"
  474.              "        flags: $%06lx\n"
  475.              "        creation time: %lu\n"
  476.              "        modification time: %lu\n"
  477.              "        time scale: %ld\n"
  478.              "        duration: %ld\n"
  479.              "        language: %ld\n"
  480.              "        quality: %ld\n"
  481.              "\n",y.LSH(head.head.version,-24),
  482.                   head.head.version MOD y.LSH(1,24),
  483.                   head.head.creation,
  484.                   head.head.modification,
  485.                   head.timeScale,
  486.                   head.duration,
  487.                   head.language,
  488.                   head.quality);
  489.   END;
  490. (* \\\ $END *)
  491.  
  492.   mediaHead:=head;
  493.   RETURN TRUE;
  494. END ReadMDHD;
  495. (* \\\ ------------------------------------------------------------------------- *)
  496.  
  497. (* /// ------------------------ "PROCEDURE ReadHDLR()" ------------------------- *)
  498. PROCEDURE ReadHDLR(size: LONGINT): BOOLEAN;
  499.  
  500. VAR     head: g.HandlerReference;
  501.  
  502. BEGIN
  503.   IF size>SIZE(head) THEN
  504.     d.PrintF("wrong size\n");
  505.     RETURN FALSE;
  506.   END;
  507.   io.Read(g.qtFile,y.ADR(head),size);
  508. (* /// "$IF RUNDEBUG" *)
  509.   IF o.debug THEN
  510.     d.PrintF("        version: %ld\n"
  511.              "        flags: $%06lx\n",y.LSH(head.version,-24),
  512.                                        head.version MOD y.LSH(1,24));
  513.     d.PrintF("        type: "); cu.PrintFCC(head.type); d.PrintF("\n");
  514.     d.PrintF("        subType: "); cu.PrintFCC(head.subType); d.PrintF("\n");
  515.     d.PrintF("        manufacturer: %ld\n"
  516.              "        flags: $%08lx\n"
  517.              "        flagMask: $%08lx\n",head.manufacturer,
  518.                                           head.flags,
  519.                                           head.flagMask);
  520.     d.PrintF("        name: "); cu.PrintName(head.name); d.PrintF("\n\n");
  521.  
  522.   END;
  523. (* \\\ $END *)
  524.  
  525.   RETURN TRUE;
  526. END ReadHDLR;
  527. (* \\\ ------------------------------------------------------------------------- *)
  528.  
  529. (* /// ------------------------ "PROCEDURE ParseMDIA()" ------------------------ *)
  530. PROCEDURE ParseMDIA(size: LONGINT): LONGINT;
  531.  
  532. VAR     atom: g.Atom;
  533.         errVal: LONGINT;
  534.  
  535. BEGIN
  536.   errVal:=g.noError;
  537.   WHILE (size>0) & (errVal=g.noError) DO
  538.     io.Read(g.qtFile,y.ADR(atom),SIZE(atom));
  539.     DEC(size,atom.size);
  540.     DEC(atom.size,SIZE(atom));
  541. (* /// "$IF RUNDEBUG" *)
  542.     IF o.debug THEN
  543.       d.PrintF("      mdia id: "); cu.PrintFCC(atom.id); d.PrintF(", size: %ld\n",atom.size);
  544.     END;
  545. (* \\\ $END *)
  546.     CASE atom.id OF
  547.     | idmdhd: IF ~ReadMDHD(atom.size) THEN errVal:=g.unknownError; END;
  548.     | idhdlr: IF ~ReadHDLR(atom.size) THEN errVal:=g.unknownError; END;
  549.     | idminf: errVal:=ParseMINF(atom.size);
  550.     | idudta: io.Skip(g.qtFile,atom.size);
  551.     ELSE
  552. (* /// "$IF RUNDEBUG" *)
  553.       IF o.debug THEN d.PrintF("unknown mdia atom\n"); END;
  554. (* \\\ $END *)
  555.       io.Skip(g.qtFile,atom.size);
  556.     END;
  557.  
  558.     IF d.ctrlC IN e.SetSignal(LONGSET{},LONGSET{d.ctrlC}) THEN errVal:=d.break; END;
  559.     IF ~g.qtFile.readOk THEN errVal:=g.readError; END;
  560.   END;
  561.   RETURN errVal;
  562. END ParseMDIA;
  563. (* \\\ ------------------------------------------------------------------------- *)
  564. (* \\\ *)
  565.  
  566. (* /// "TRAK" *)
  567. (* /// ------------------------ "PROCEDURE ReadTKHD()" ------------------------- *)
  568. PROCEDURE ReadTKHD(size: LONGINT): BOOLEAN;
  569.  
  570. VAR     head: g.TrackHeader;
  571.         flags: LONGSET;
  572.         s: e.STRING;
  573.         w: e.STRING;
  574.         h: e.STRING;
  575.  
  576. BEGIN
  577.   IF size#SIZE(head) THEN
  578.     d.PrintF("wrong size\n");
  579.     RETURN FALSE;
  580.   END;
  581.   io.Read(g.qtFile,y.ADR(head),size);
  582. (* /// "$IF RUNDEBUG" *)
  583.   IF o.debug THEN
  584.     mu.real2str(fp.FP16toREAL(head.volume),s,4);
  585.     mu.real2str(fp.FP32toREAL(head.width),w,4);
  586.     mu.real2str(fp.FP32toREAL(head.height),h,4);
  587.     flags:=y.VAL(LONGSET,head.head.version)*LONGSET{0..23};
  588.     d.PrintF("      version: %ld\n",y.LSH(head.head.version,-24));
  589.     d.PrintF("      flags: $%06lx =",y.VAL(LONGINT,flags));
  590.     IF trackEnabled IN flags THEN d.PrintF(" enabled"); END;
  591.     IF trackInMovie IN flags THEN d.PrintF(" inMovie"); END;
  592.     IF trackInPreview IN flags THEN d.PrintF(" inPreview"); END;
  593.     IF trackInPoster IN flags THEN d.PrintF(" inPoster"); END;
  594.     d.PrintF("\n"
  595.              "      creation time: %lu\n"
  596.              "      modification time: %lu\n"
  597.              "      track ID: %ld\n"
  598.              "      duration: %ld\n"
  599.              "      layer: %ld\n"
  600.              "      alt group: %ld\n"
  601.              "      volume: %s\n"
  602.              "      width: %s\n"
  603.              "      height: %s\n"
  604.              "\n",head.head.creation,
  605.                   head.head.modification,
  606.                   head.trackID,
  607.                   head.duration,
  608.                   head.layer,
  609.                   head.altGroup,
  610.                   y.ADR(s),
  611.                   y.ADR(w),
  612.                   y.ADR(h));
  613.   END;
  614. (* \\\ $END *)
  615.  
  616.   trackHead:=head;
  617.   RETURN TRUE;
  618. END ReadTKHD;
  619. (* \\\ ------------------------------------------------------------------------- *)
  620.  
  621. (* /// ------------------------ "PROCEDURE ReadELST()" ------------------------- *)
  622. PROCEDURE ReadELST(size: LONGINT): BOOLEAN;
  623.  
  624. VAR     cnt: LONGINT;
  625.         s: e.STRING;
  626.  
  627. BEGIN
  628.   IF size=0 THEN RETURN TRUE; END;
  629.   size:=io.GetMSBLong(g.qtFile);
  630.   io.Skip(g.qtFile,8); (* "elst", flags/version *)
  631.   editEntries:=io.GetMSBLong(g.qtFile);
  632.   DEC(size,16);
  633.   ol.New(edits,editEntries*SIZE(g.EditList));
  634.   io.Read(g.qtFile,edits,editEntries*SIZE(g.EditList));
  635.   IF edits[0].mediaTime=0FFFFFFFFH THEN
  636.     INC(trackInitDuration,edits[0].duration);
  637. (* /// "$IF RUNDEBUG" *)
  638.     IF o.debug THEN d.PrintF("      elst init duration: %ld\n\n",trackInitDuration); END;
  639. (* \\\ $END *)
  640.   ELSIF edits[0].mediaTime#0 THEN
  641.     INC(trackStartOffset,edits[0].mediaTime);
  642. (* /// "$IF RUNDEBUG" *)
  643.     IF o.debug THEN d.PrintF("      elst start offset: %ld\n\n",trackStartOffset); END;
  644. (* \\\ $END *)
  645.   END;
  646. (* /// "$IF RUNDEBUG" *)
  647.   IF o.debug THEN
  648.     FOR cnt:=0 TO editEntries-1 DO
  649.       mu.real2str(fp.FP32toREAL(edits[cnt].mediaRate),s,4);
  650.       d.PrintF("      entry %2ld: duration: %ld\n"
  651.                "                time: %ld\n"
  652.                "                rate: %s\n"
  653.                "\n",cnt,edits[cnt].duration,edits[cnt].mediaTime,y.ADR(s));
  654.     END;
  655.   END;
  656. (* \\\ $END *)
  657.   RETURN TRUE;
  658. END ReadELST;
  659. (* \\\ ------------------------------------------------------------------------- *)
  660.  
  661. (* /// ------------------------ "PROCEDURE ParseTRAK()" ------------------------ *)
  662. PROCEDURE ParseTRAK(size: LONGINT): LONGINT;
  663.  
  664. VAR     atom: g.Atom;
  665.         errVal: LONGINT;
  666.  
  667. BEGIN
  668.   videoFlag:=FALSE;
  669.   audioFlag:=FALSE;
  670.   trackStartOffset:=0;
  671.   trackInitDuration:=0;
  672.   edits:=NIL;
  673.   editEntries:=0;
  674.   currentTrack:=NIL;
  675.  
  676.   errVal:=g.noError;
  677.   WHILE (size>0) & (errVal=g.noError) DO
  678.     io.Read(g.qtFile,y.ADR(atom),SIZE(atom));
  679.     DEC(size,atom.size);
  680.     DEC(atom.size,SIZE(atom));
  681. (* /// "$IF RUNDEBUG" *)
  682.     IF o.debug THEN
  683.       d.PrintF("    trak id: "); cu.PrintFCC(atom.id); d.PrintF(", size: %ld\n",atom.size);
  684.     END;
  685. (* \\\ $END *)
  686.     CASE atom.id OF
  687.     | idtkhd: IF ~ReadTKHD(atom.size) THEN errVal:=g.unknownError; END;
  688.     | idedts: IF ~ReadELST(atom.size) THEN errVal:=g.unknownError; END;
  689.     | idmdia: errVal:=ParseMDIA(atom.size);
  690.     | idclip,
  691.       idmatt,
  692.       idtref,
  693.       idload,
  694.       idimap,
  695.       idudta: io.Skip(g.qtFile,atom.size);
  696.     ELSE
  697. (* /// "$IF RUNDEBUG" *)
  698.       IF o.debug THEN d.PrintF("unknown trak atom\n"); END;
  699. (* \\\ $END *)
  700.       io.Skip(g.qtFile,atom.size);
  701.     END;
  702.  
  703.     IF d.ctrlC IN e.SetSignal(LONGSET{},LONGSET{d.ctrlC}) THEN errVal:=d.break; END;
  704.     IF ~g.qtFile.readOk THEN errVal:=g.readError; END;
  705.     IF trackHead.duration=0 THEN
  706.       io.Skip(g.qtFile,size);
  707.       size:=0;
  708.     END;
  709.   END;
  710.  
  711.   RETURN errVal;
  712. END ParseTRAK;
  713. (* \\\ ------------------------------------------------------------------------- *)
  714. (* \\\ *)
  715.  
  716. (* /// "MOOV" *)
  717. (* /// ------------------------ "PROCEDURE ReadMVHD()" ------------------------- *)
  718. PROCEDURE ReadMVHD(size: LONGINT): BOOLEAN;
  719.  
  720. VAR     head: g.MovieHeader;
  721.         s1: e.STRING;
  722.         s2: e.STRING;
  723.  
  724. BEGIN
  725.   IF size#SIZE(head) THEN
  726.     d.PrintF("wrong size\n");
  727.     RETURN FALSE;
  728.   END;
  729.   io.Read(g.qtFile,y.ADR(head),size);
  730. (* /// "$IF RUNDEBUG" *)
  731.   IF o.debug THEN
  732.     mu.real2str(fp.FP32toREAL(head.rate),s1,4);
  733.     mu.real2str(fp.FP16toREAL(head.volume),s2,4);
  734.     d.PrintF("    version: %ld\n"
  735.              "    flags: $%06lx\n"
  736.              "    creation time: %lu\n"
  737.              "    modification time: %lu\n"
  738.              "    time scale: %ld\n"
  739.              "    duration: %ld\n"
  740.              "    rate: %s\n"
  741.              "    volume: %s\n"
  742.              "    preview time: %ld\n"
  743.              "    preview duration: %ld\n"
  744.              "    poster time: %ld\n"
  745.              "    selection time: %ld\n"
  746.              "    selection duration: %ld\n"
  747.              "    currentTime: %ld\n"
  748.              "    next track ID: %ld\n"
  749.              "\n",y.LSH(head.head.version,-24),
  750.                   head.head.version MOD y.LSH(1,24),
  751.                   head.head.creation,
  752.                   head.head.modification,
  753.                   head.timeScale,
  754.                   head.duration,
  755.                   y.ADR(s1),
  756.                   y.ADR(s2),
  757.                   head.previewTime,
  758.                   head.previewDuration,
  759.                   head.posterTime,
  760.                   head.selectTime,
  761.                   head.selectDuration,
  762.                   head.currentTime,
  763.                   head.nextTrackID);
  764.   END;
  765. (* \\\ $END *)
  766.   g.animInfo.mvhd:=head;
  767.  
  768.   RETURN TRUE;
  769. END ReadMVHD;
  770. (* \\\ ------------------------------------------------------------------------- *)
  771.  
  772. (* /// ------------------------ "PROCEDURE ParseMOOV()" ------------------------ *)
  773. PROCEDURE ParseMOOV * (size: LONGINT): LONGINT;
  774.  
  775. VAR     atom: g.Atom;
  776.         errVal: LONGINT;
  777.  
  778. BEGIN
  779.   errVal:=g.noError;
  780.   WHILE (size>0) & (errVal=g.noError) DO
  781.     io.Read(g.qtFile,y.ADR(atom),SIZE(atom));
  782.     DEC(size,atom.size);
  783.     DEC(atom.size,SIZE(atom));
  784. (* /// "$IF RUNDEBUG" *)
  785.     IF o.debug THEN
  786.       d.PrintF("  moov id: "); cu.PrintFCC(atom.id); d.PrintF(", size: %ld\n",atom.size);
  787.     END;
  788. (* \\\ $END *)
  789.     CASE atom.id OF
  790.     | idmvhd: IF ~ReadMVHD(atom.size) THEN errVal:=g.unknownError; END;
  791.     | idtrak: errVal:=ParseTRAK(atom.size);
  792.     | idclip,
  793.       idctab,
  794.       idudta: io.Skip(g.qtFile,atom.size);
  795.     ELSE
  796. (* /// "$IF RUNDEBUG" *)
  797.       IF o.debug THEN d.PrintF("unknown moov atom\n"); END;
  798. (* \\\ $END *)
  799.       io.Skip(g.qtFile,atom.size);
  800.     END;
  801.  
  802.     IF d.ctrlC IN e.SetSignal(LONGSET{},LONGSET{d.ctrlC}) THEN errVal:=d.break; END;
  803.     IF ~g.qtFile.readOk THEN errVal:=g.readError; END;
  804.   END;
  805.  
  806.   IF errVal=g.noError THEN
  807.     IF ~es.ListEmpty(g.animInfo.videoTracks) THEN
  808.       cu.SortCodecs(g.animInfo.videoTracks);
  809.       CorrectTrackValues(g.animInfo.videoTracks);
  810.     END;
  811.     IF ~es.ListEmpty(g.animInfo.audioTracks) THEN
  812.       cu.SortCodecs(g.animInfo.audioTracks);
  813.       CorrectTrackValues(g.animInfo.audioTracks);
  814.     END;
  815.   END;
  816.  
  817.   RETURN errVal;
  818. END ParseMOOV;
  819. (* \\\ ------------------------------------------------------------------------- *)
  820. (* \\\ *)
  821.  
  822. END CyberQTParser.
  823.  
  824.